package com.minimalist.lindi.service.impl;

import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.bean.copier.CopyOptions;
import cn.hutool.core.lang.Assert;
import cn.hutool.http.HttpStatus;
import com.minimalist.common.config.exception.BusinessException;
import com.minimalist.common.config.mybatis.bo.PageResp;
import com.minimalist.common.entity.basic.enums.RespEnum;
import com.minimalist.common.entity.basic.vo.file.FileUploadRespVO;
import com.minimalist.common.entity.basic.vo.file.FileVO;
import com.minimalist.common.entity.lindi.po.LindiTradeApplicationTemplateContract;
import com.minimalist.common.entity.lindi.vo.contracttemplate.LindiContractTemplateVO;
import com.minimalist.common.entity.lindi.vo.tradeapplicationtemplatecontract.LindiTradeApplicationTemplateContractQueryVO;
import com.minimalist.common.entity.lindi.vo.tradeapplicationtemplatecontract.LindiTradeApplicationTemplateContractVO;
import com.minimalist.common.feign.client.basic.FileFeignClient;
import com.minimalist.common.response.R;
import com.minimalist.common.utils.UnqIdUtil;
import com.minimalist.lindi.manager.ContractTemplateManager;
import com.minimalist.lindi.mapper.LindiTradeApplicationTemplateContractMapper;
import com.minimalist.lindi.service.LindiTradeApplicationTemplateContractService;
import com.mybatisflex.core.paginate.Page;
import com.mybatisflex.spring.service.impl.ServiceImpl;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.time.LocalDateTime;
import java.util.*;
import java.util.function.Function;
import java.util.stream.Collectors;

/**
 * 林地指标交易平台_交易申请合同模板 服务层实现。
 *
 * @author 11987
 * @since 2025-06-04
 */
@Service
public class LindiTradeApplicationTemplateContractServiceImpl
        extends ServiceImpl<LindiTradeApplicationTemplateContractMapper
        , LindiTradeApplicationTemplateContract> implements LindiTradeApplicationTemplateContractService{

    private static final Logger logger = LoggerFactory.getLogger(LindiTradeApplicationTemplateContractServiceImpl.class);

    @Autowired
    private LindiTradeApplicationTemplateContractMapper mapper;

    @Autowired
    private ContractTemplateManager contractTemplateManager;

    @Autowired
    private FileFeignClient fileFeignClient;

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void addTradeApplicationTemplateContract(LindiTradeApplicationTemplateContractVO tradeApplicationTemplateContractVO){
        LindiTradeApplicationTemplateContract record = BeanUtil.copyProperties(tradeApplicationTemplateContractVO,
                LindiTradeApplicationTemplateContract.class);
        record.setTradeApplicationContractFileId(UnqIdUtil.uniqueId());
        int insert = mapper.insert(record, true);
        Assert.isTrue(insert == 1, () -> new BusinessException("添加交易申请合同模板失败"));
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void deleteTradeApplicationTemplateContractByTradeApplicationTemplateContractId(
            Long tradeApplicationTemplateContractId){
        LindiTradeApplicationTemplateContract record = mapper
                .selectTradeApplicationTemplateContractByTradeApplicationTemplateContractId
                        (tradeApplicationTemplateContractId);
        Assert.notNull(record, () -> new BusinessException("交易申请合同模板不存在"));
        List<Long> fileIds = new ArrayList<>();
        if (record.getFileId() != null){
            fileIds.add(record.getFileId());
        }
        if (!fileIds.isEmpty()){
            try{
                R<Void> result = fileFeignClient.deleteBatchFiles(fileIds);
                if (!Objects.equals(result.getCode(), RespEnum.SUCCESS.getCode())){
                    logger.warn("删除合同模板文件失败，文件IDs: {}, 错误信息: {}", fileIds, result.getMessage());
                }
            } catch (Exception e){
                logger.warn("删除合同模板文件异常，文件IDs: {}, 异常信息: {}", fileIds, e.getMessage());
            }
        }
        int delete = mapper.delete(record);
        Assert.isTrue(delete == 1, () -> new BusinessException("删除交易申请合同模板失败"));
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void updateTradeApplicationTemplateContractByTradeApplicationTemplateContractId(
            LindiTradeApplicationTemplateContractVO tradeApplicationTemplateContractVO){
        LindiTradeApplicationTemplateContract record = mapper
                .selectTradeApplicationTemplateContractByTradeApplicationTemplateContractId(tradeApplicationTemplateContractVO
                        .getTradeApplicationContractFileId());
        Assert.notNull(record, () -> new BusinessException("交易申请合同模板不存在"));
        BeanUtil.copyProperties(tradeApplicationTemplateContractVO, record,
                CopyOptions.create().ignoreNullValue());
        int update = mapper.update(record);
        Assert.isTrue(update == 1, () -> new BusinessException("更新交易申请合同模板失败"));
    }

    @Override
    public PageResp<LindiTradeApplicationTemplateContractVO>
    getPageTradeApplicationTemplateContractList(
            LindiTradeApplicationTemplateContractQueryVO queryVO){
        Page<LindiTradeApplicationTemplateContract> page = mapper.selectPageTradeApplicationTemplateContractList(queryVO);
        List<LindiTradeApplicationTemplateContractVO> voList = BeanUtil.copyToList(page.getRecords(),
                LindiTradeApplicationTemplateContractVO.class);

        // 收集所有文件ID
        List<Long> fileIds = page.getRecords().stream().map(
                LindiTradeApplicationTemplateContract::getFileId).toList();

        // 批量获取文件信息
        Map<Long, FileVO> fileMap = new HashMap<>(16);

        if (!fileIds.isEmpty()){
            R<List<FileVO>> fileResult = fileFeignClient.getFileListByFileIds(fileIds);
            if (fileResult.getCode() == HttpStatus.HTTP_OK
                    && fileResult.getData() != null){
                fileMap = fileResult.getData().stream()
                        .collect(Collectors.toMap(FileVO::getFileId
                                , Function.identity()));
            }
        }

        // 设置文件信息到VO中
        for (LindiTradeApplicationTemplateContractVO vo : voList){
            if (vo.getFileId() != null){
                vo.setFile(fileMap.get(vo.getFileId()));
            }
        }

        return new PageResp<>(voList, voList.size());
    }

    @Override
    public LindiTradeApplicationTemplateContractVO getTradeApplicationTemplateContractByTradeApplicationTemplateContractId(
            Long tradeApplicationTemplateContractId){
        LindiTradeApplicationTemplateContract record = mapper
                .selectTradeApplicationTemplateContractByTradeApplicationTemplateContractId(
                        tradeApplicationTemplateContractId);
        Assert.notNull(record, () -> new BusinessException("交易申请合同模板不存在"));
        LindiTradeApplicationTemplateContractVO lindiTradeApplicationTemplateContractVO
                = BeanUtil.copyProperties(record
                , LindiTradeApplicationTemplateContractVO.class);

        R<FileVO> fileResult = fileFeignClient
                .getFileByFileId(record.getFileId());
        Assert.isTrue(fileResult.getCode() == HttpStatus.HTTP_OK
                        && fileResult.getData() != null
                , () -> new BusinessException("获取合同文件失败"));
        lindiTradeApplicationTemplateContractVO.setFile(
                fileResult.getData());
        return lindiTradeApplicationTemplateContractVO;
    }

    @Override
    public void deleteTradeApplicationTemplateContractFileByFileId(Long fileId){
    }

    @Override
    public LindiTradeApplicationTemplateContractVO generateTemplateContract(Long tradeApplicationId, Long contractTemplateId
            , String contractType, Long createId, Long tanantId){
        R<FileUploadRespVO> fileUploadRespVO = contractTemplateManager
                .generateContract(tradeApplicationId, contractTemplateId
                        , contractType, createId, tanantId);
        LindiTradeApplicationTemplateContractVO tradeApplicationTemplateContractVO
                = new LindiTradeApplicationTemplateContractVO();
        tradeApplicationTemplateContractVO.setTradeApplicationContractFileId(
                UnqIdUtil.uniqueId());
        tradeApplicationTemplateContractVO.setTradeApplicationId(tradeApplicationId);
        tradeApplicationTemplateContractVO.setContractType(contractType);
        tradeApplicationTemplateContractVO.setCreateId(createId);
        tradeApplicationTemplateContractVO.setUpdateId(createId);
        LocalDateTime now = LocalDateTime.now();
        tradeApplicationTemplateContractVO.setCreateTime(now);
        tradeApplicationTemplateContractVO.setUpdateTime(now);
        tradeApplicationTemplateContractVO.setFileId(
                fileUploadRespVO.getData().getFileId());
        LindiTradeApplicationTemplateContract lindiTradeApplicationTemplateContract = BeanUtil.copyProperties(tradeApplicationTemplateContractVO
                , LindiTradeApplicationTemplateContract.class);
        int insert = mapper.insert(lindiTradeApplicationTemplateContract);
        Assert.isTrue(insert == 1, () -> new BusinessException("插入交易申请合同模板失败"));
        return tradeApplicationTemplateContractVO;
    }

    @Override
    public List<LindiContractTemplateVO> getContractTemplateList(){
        return contractTemplateManager.getContractTemplateList();
    }
}
